package thread;

import java.io.*;
import java.net.ServerSocket;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
import java.util.Collection;
import java.util.HashMap;
import java.util.Map;

import static jdk.nashorn.internal.objects.NativeArray.forEach;

/**
 * @Author: Miyako
 * @Date: 2024-07-22-8:19
 * @Description: 多人聊天服务器
 */

public class MapChartServer {
//    private List<PrintWriter> pws = new ArrayList<>();
    private Map<String,PrintWriter> pws = new HashMap<>();
    private class ClientHander implements Runnable{
        private Socket socket;
        private String host;
        ClientHander(Socket socket){
            this.socket = socket;
            host = socket.getInetAddress().getHostAddress();
        }
        public void run(){
            PrintWriter pw = null;
            String data;
            try{
                BufferedReader br = new BufferedReader(
                        new InputStreamReader(
                                socket.getInputStream(), StandardCharsets.UTF_8));
                pw = new PrintWriter(
                        new BufferedWriter(
                                new OutputStreamWriter(
                                        socket.getOutputStream(),StandardCharsets.UTF_8)),true);

                String nickName=br.readLine();
                synchronized (MapChartServer.this) {
                    pws.put(nickName,pw);//将键值对添加到集合中
                }
                pw.println("欢迎"+nickName+"加入聊天室");
                while((data = br.readLine())!=null){
                    System.out.println(host+":"+data);
                    if (data.startsWith("@")){
                        sendMsgToOne(data,nickName);
                    }else {
                        sendMsgToAll(data,nickName);//广播
                    }
                }
            }catch (Exception e){
                e.printStackTrace();
            }finally {
                synchronized (MapChartServer.this){
                    pws.remove(pw);
                    try {
                        if (socket != null) {
                            socket.close();
                        }
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
            }
        }
    }
    private void sendMsgToOne(String data,String nickName){//私聊
        //将内容按分号划分为两个字符串
        data = data.substring(1);//去除第一个@
        String[] dataArray = data.split(":",2);//将其划分为键值对格式
        pws.get(dataArray[0]).println(nickName+":"+dataArray[1]);//通过昵称key值,获取对应的客户输出流
    }
    private void sendMsgToAll(String data,String nickName){//广播
        synchronized (MapChartServer.this) {
            pws.forEach((k, v)->{if (k!=nickName)pws.get(k).println(nickName+":"+data);});//广播但不发送重复内容
        }
    }
    private ServerSocket serverSocket;
    private static final int port;
    static {
        port=9288;
    }
    MapChartServer(){
        try{
            System.out.println("Server Starting ...");
            serverSocket = new ServerSocket(port);
            System.out.println("Server Start ok!");
        }catch (IOException e){
            e.printStackTrace();
            System.out.println("Server Start deft");
            System.exit(-1);
        }

    }
    public  void start(){
        while(true){
            try{
                System.out.println("Client Linking...");
                Socket socket = serverSocket.accept();
                System.out.println("Client Link ok!");
                new Thread(new ClientHander(socket)).start();
            }catch (IOException e){
                e.printStackTrace();
                System.out.println("Client Link defeat");
            }
        }
    }



    public static void main(String[] args) {
        new MapChartServer().start();
        Thread.currentThread().getName();
    }
}

